package com.ycsyxt.controller;

import java.io.IOException;
import java.util.HashMap;
import java.util.stream.Collectors;
import com.ycsyxt.service.StorageService;
import com.ycsyxt.exception.StorageFileNotFoundException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.Resource;
import org.springframework.http.HttpHeaders;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.servlet.mvc.method.annotation.MvcUriComponentsBuilder;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;

import javax.servlet.http.HttpServletRequest;

/**
 * @author ycs
 * @date 2021/4/23
 */
@Controller
public class FileUploadController {

    private final StorageService storageService;

    @Autowired
    public FileUploadController(StorageService storageService) {
        this.storageService = storageService;
    }

    @GetMapping("/")
    @ResponseBody
    public HashMap<String, Object> listUploadedFiles() throws IOException {
        HashMap<String, Object> map = new HashMap<>();
        map.put("files", storageService.loadAll().map(
                path -> MvcUriComponentsBuilder.fromMethodName(FileUploadController.class,
                        "serveFile", path.getFileName().toString()).build().toUri().toString())
                .filter(url -> url.indexOf(".jpg") > 1 || url.indexOf(".png") > 1)
                .collect(Collectors.toList()));
        return map;
    }

    @GetMapping("/files/{filename:.+}")
    @ResponseBody
    public ResponseEntity<Resource> serveFile(@PathVariable String filename) {
        Resource file = storageService.loadAsResource(filename);
        return ResponseEntity.ok().header(HttpHeaders.CONTENT_DISPOSITION,
                "attachment; filename=\"" + file.getFilename() + "\"").body(file);
    }

    @PutMapping("/file/rename")
    @ResponseBody
    public ResponseEntity<?> renameFile(@RequestParam String oldName, @RequestParam String newName) {
        storageService.rename(oldName, newName);
        return ResponseEntity.ok().header(HttpHeaders.CONTENT_DISPOSITION).build();
    }

    @GetMapping("/plants/**")
    @ResponseBody
    public ResponseEntity<Resource> staticFile(HttpServletRequest request) {
        String filename = request.getRequestURI().substring(1);
        Resource file = storageService.loadAsResource(filename);
        return ResponseEntity.ok().body(file);
    }

    @PostMapping("/")
    public String handleFileUpload(@RequestParam("file") MultipartFile file,
                                   RedirectAttributes redirectAttributes) {
        storageService.store(file);
        redirectAttributes.addFlashAttribute("message",
                "You successfully uploaded " + file.getOriginalFilename() + "!");
        return "redirect:/";
    }

    @ExceptionHandler(StorageFileNotFoundException.class)
    public ResponseEntity<?> handleStorageFileNotFound(StorageFileNotFoundException exc) {
        return ResponseEntity.notFound().build();
    }

}
